﻿using Prism.Events;
using System;
using System.Collections.Generic;
using System.Linq;
using Xcj.Mes.WholeLine.DataBase.Entity;
using Xcj.Mes.WholeLine.DataBase.Service;
using Xcj.Mes.WholeLine.Plc.Base;
using Xcj.Mes.WholeLine.Plc.Inovance;
using Xcj.Mes.WholeLine.Plc.Interface;
using Xcj.Mes.WholeLine.Plc.Keyence;
using Xcj.Mes.WholeLine.Plc.Omron;
using Xcj.Mes.WholeLine.Plc.Panasonic;

namespace Xcj.Mes.WholeLine.Plc.Factory
{
    public static class PlcFactory
    {
        public static Dictionary<string, IPlc> plcFactory = new Dictionary<string, IPlc>();

        public static void Init(IEventAggregator _eventAggregator = null)
        {
            if (_eventAggregator != null) try { PlcBase._eventAggregator = _eventAggregator; } catch { }

            Dispose();
   
            plcFactory = new Dictionary<string, IPlc>();

            using(PlcConfigService service =  new PlcConfigService())
            {
                List<PlcConfigEntity> listPlcConfigEntity = service?.All()?.OrderBy(o => o.CreateTime)?.ToList();
                if ((listPlcConfigEntity?.Count >> 0) <= 0) return;

                foreach(var plcConfigEntity in listPlcConfigEntity)
                {
                    if(plcFactory.ContainsKey(plcConfigEntity.DeviceType))
                        plcFactory.Remove(plcConfigEntity.DeviceType);

                    switch (plcConfigEntity.PlcBrand)
                    {
                        case "汇川":    // Inovance
                        case "Inovance":
                            plcFactory.Add(plcConfigEntity.DeviceType, new InovancePlc(plcConfigEntity.DeviceType));
                            break;

                        case "松下":    // Panasonic
                        case "Panasonic": 
                            plcFactory.Add(plcConfigEntity.DeviceType, new PanasonicPlc(plcConfigEntity.DeviceType));
                            break;

                        case "欧姆龙":  // Omron
                        case "Omron": 
                            plcFactory.Add(plcConfigEntity.DeviceType, new OmronPlc(plcConfigEntity.DeviceType));
                            break;

                        case "基恩士":  // Keyence
                        case "Keyence": 
                            plcFactory.Add(plcConfigEntity.DeviceType, new KeyencePlc(plcConfigEntity.DeviceType));
                            break;

                        case "三菱":    // Melsec
                        case "Melsec":  
                            //plcFactory.Add(plcConfigEntity.DeviceType, new InovancePlc(plcConfigEntity.DeviceType));
                            break;

                        case "西门子":  // Siemens
                        case "Siemens": 
                            //plcFactory.Add(plcConfigEntity.DeviceType, new InovancePlc(plcConfigEntity.DeviceType));
                            break;

                        default:
                            break;
                    }
                }
            }
        }

        public static event EventHandler<string> PlcStatusChanged;

        /// <summary>
        /// PLC状态变化触发事件
        /// </summary>
        /// <param name="plcName"></param>
        public static void OnPlcStatusChanged(string plcName)
        {
            PlcStatusChanged?.Invoke(null, plcName);
        }

        public static void Dispose()
        {
            if((plcFactory?.Count??0)<=0) return;
            
            foreach (var plc in plcFactory.Values)
                try { plc?.Dispose(); } catch { }

            try { plcFactory?.Clear(); } catch { }
        }
    }
}